﻿using System.Collections.Generic;
using System.Linq;
using Engine;
using Engine.Graphics;
using Game;
using Mekiasm.Common;

namespace Mekiasm
{
    public abstract class ComplexModelItem : OreCube
    {
        public ModelItem[] ModelItems;
        public float IconScale = 1f;
        public Model model;
        public bool IsAllowRotate = true;
        public ComplexModelItem(ModelItem[] modelItems, string modelname, string n) : base(n)
        {
            ModelItems = modelItems;
            model = ContentManager.Get<Model>("Mekiasm/Models/" + modelname);
            InitDrawModel();
        }
        public void InitDrawModel()
        {
            for (int i = 0; i < ModelItems.Length; i++)
            {
                ModelItem modelitem = ModelItems.FirstOrDefault(p => p.Texture2D != null && p.textureName == ModelItems[i].textureName);
                if (modelitem != null && modelitem.Texture2D != null)
                {
                    ModelItems[i].Load(model, modelitem.Texture2D);
                }
                else
                {
                    Texture2D texture = null;
                    if (ModelItems[i].textureName != null) texture = ContentManager.Get<Texture2D>("Mekiasm/Textures/Model/" + ModelItems[i].textureName);
                    ModelItems[i].Load(model, texture);
                }
            }
        }
        public override BlockPlacementData GetPlacementValue(SubsystemTerrain subsystemTerrain, ComponentMiner componentMiner, int value, TerrainRaycastResult raycastResult)
        {
            return ILibrary.GetPlacementValue(subsystemTerrain, componentMiner, value, raycastResult);
        }
        public override void GenerateTerrainVertices(Block block, BlockGeometryGenerator generator, TerrainGeometry geometry, int value, int x, int y, int z)
        {
            var modelItems = new ModelItem[ModelItems.Length];
            for (int i = 0; i < ModelItems.Length; i++)
            {
                modelItems[i] = new ModelItem(ModelItems[i].meshName, ModelItems[i].textureName);
                modelItems[i].Load(model, ModelItems[i].Texture2D);
            }
            int rotate = ILibrary.GetDirection(value);
            if (!IsAllowRotate) rotate = 0;
            for (int i = 0; i < modelItems.Length; i++)
            {
                if (modelItems[i].Texture2D == null) continue;
                modelItems[i].Transform(model, Matrix.CreateRotationY(MathUtils.PI * rotate / 2));
                generator.GenerateMeshVertices(block, x, y, z, modelItems[i].TransformedBlockMesh, Color.White, null, geometry.GetGeometry(modelItems[i].Texture2D).SubsetOpaque);
            }
        }
        public override void DrawBlock(PrimitivesRenderer3D primitivesRenderer, int value, Color color, float size, ref Matrix matrix, DrawBlockEnvironmentData environmentData)
        {
            for (int i = 0; i < ModelItems.Length; i++)
            {
                if (ModelItems[i].Texture2D == null) continue;
                BlocksManager.DrawMeshBlock(primitivesRenderer, ModelItems[i].BlockMesh, ModelItems[i].Texture2D, Color.White, size * IconScale, ref matrix, environmentData);
            }
        }
        public override bool IsFaceTransparent(SubsystemTerrain subsystemTerrain, int face, int value)
        {
            return true;
        }
        public override void GetDropValues(SubsystemTerrain subsystemTerrain, int oldValue, int newValue, int toolLevel, List<BlockDropValue> dropValues, out bool showDebris)
        {
            showDebris = true;
            dropValues.Add(new BlockDropValue() { Value = ILibrary.GetBasicValue(oldValue), Count = 1 });
        }
        public override BoundingBox[] GetCustomCollisionBoxes(SubsystemTerrain terrain, MovingBlock value)
        {
            List<BoundingBox> boundingBoxes = new List<BoundingBox>();
            for (int i = 0; i < ModelItems.Length; i++)
            {
                boundingBoxes.Add(ModelItems[i].BlockMesh.CalculateBoundingBox());
            }
            if (boundingBoxes.Count == 0)
            {
                boundingBoxes.Add(new BoundingBox(Vector3.Zero, Vector3.One));
            }
            return boundingBoxes.ToArray();
        }
        public override BoundingBox[] GetCustomInteractionBoxes(SubsystemTerrain terrain, MovingBlock value)
        {
            return GetCustomCollisionBoxes(terrain, value);
        }
        public override float GetDigResilience(int value)
        {
            return 6f;
        }
        public override bool IsInteractive(SubsystemTerrain subsystemTerrain, int value)
        {
            return true;
        }
    }
}
